package cnki.tpi.kbatis.executor;

import cnki.tpi.kbatis.config.Configuration;
import cnki.tpi.kbatis.config.MappedStatement;
import cnki.tpi.kbatis.handler.ResultSetHandler;
import cnki.tpi.kbatis.handler.StatementHandler;
import cnki.tpi.kbatis.sqlsource.BoundSql;
import cnki.tpi.kbatis.utils.DataSourceUtil;
import com.kbase.jdbc.ResultSetImpl;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.sql.Connection;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @ClassName CacheExecutor
 * @Description 执行JDBC 代码
 * @Author 小黄
 * @Date 2019/11/15 20:18
 * @Version 1.0
 */
public class SimpleExecutor extends BaseExecutor {
    private Map<String, List<Object>> oneLevelCache = new HashMap<String, List<Object>>();
    protected final static Logger logger = LoggerFactory.getLogger(SimpleExecutor.class);



    /**
     * 查询结果封装为List<T>
     *
     * @param mappedStatement
     * @param configuration
     * @param param
     * @param boundSql
     * @return
     */
    @Override
    public List<Object> excuteQueryList(MappedStatement mappedStatement, Configuration configuration, Object param, BoundSql boundSql, Boolean isHightLight) {
        List<Object> results = null;
        Connection connection = null;
        ResultSet resultSet = null;
        String sql = null;
        try {  // 获取链接
            connection = DataSourceUtil.getConnection(configuration);
            // 获取 sql 数据
            sql = boundSql.getSql();
            StatementHandler statementHandler = new StatementHandler(mappedStatement, configuration, param, boundSql, connection, sql);
            sql = statementHandler.parameterize(statementHandler.getSql(), statementHandler.getMappedStatement(), statementHandler.getBoundSql(), statementHandler.getParam());
            logger.info(sql);
            results = oneLevelCache.get(sql);
            if (results != null) {
                return results;
            }
            results = new ArrayList<Object>();
            resultSet = statementHandler.executeQuery(sql);
            if (resultSet != null) {
                if (isHightLight) {
                    ((ResultSetImpl) resultSet).SetHitWordMarkFlag("###", "!!!");
                }
                ResultSetHandler resultSetHandler = new ResultSetHandler(resultSet, mappedStatement, results);
                resultSetHandler.handleResultSet();
            }
            oneLevelCache.put(sql, results);
        } catch (Exception e) {
            e.printStackTrace();
            logger.error(sql);
            logger.error(e.getMessage());
        } finally {
            release(connection, resultSet);
        }
        return results;
    }

    /**
     * 查询记录数
     *
     * @param mappedStatement
     * @param configuration
     * @param param
     * @param boundSql
     * @return
     */
    @Override
    public Long excuteQueryRecordNumber(MappedStatement mappedStatement, Configuration configuration, Object param, BoundSql boundSql) {
        Long record = Long.valueOf(0);
        Connection connection = null;
        ResultSet resultSet = null;
        try {  // 获取链接
            connection = DataSourceUtil.getConnection(configuration);
            // 获取 sql 数据
            String sql = boundSql.getSql();
            StatementHandler statementHandler = new StatementHandler(mappedStatement, configuration, param, boundSql, connection, sql);
            sql = statementHandler.parameterize(statementHandler.getSql(), statementHandler.getMappedStatement(), statementHandler.getBoundSql(), statementHandler.getParam());
            resultSet = statementHandler.executeQuery(sql);
            if (resultSet != null) {
                while (resultSet.next()) {
                    record = Long.parseLong(resultSet.getString(1));
                    break;
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            release(connection, resultSet);
        }
        return record;
    }

    /**
     * execute(sql)
     *
     * @param mappedStatement
     * @param configuration
     * @param param
     * @param boundSql
     * @return
     */
    @Override
    protected Boolean execute(MappedStatement mappedStatement, Configuration configuration, Object param, BoundSql boundSql) {
        Boolean flag = Boolean.FALSE;
        Connection connection = null;
        ResultSet resultSet = null;
        try {  // 获取链接
            connection = DataSourceUtil.getConnection(configuration);
            // 获取 sql 数据
            String sql = boundSql.getSql();
            StatementHandler statementHandler = new StatementHandler(mappedStatement, configuration, param, boundSql, connection, sql);
            flag = statementHandler.execute();
            System.out.println(sql);
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            release(connection, resultSet);
        }
        return flag;
    }

    /**
     * 释放资源
     *
     * @param connection
     * @param rs
     */
    private void release(Connection connection, ResultSet rs) {
        if (rs != null) {
            try {
                rs.close();
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
        if (connection != null) {
            try {
                connection.close();
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
}
